package com.example.controller;

import com.example.entity.FileEntity;
import com.example.mapper.FileMapper;
import lombok.Data;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.core.io.ByteArrayResource;
import org.springframework.core.io.InputStreamResource;
import org.springframework.core.io.Resource;
import org.springframework.http.*;
import org.springframework.util.LinkedMultiValueMap;
import org.springframework.util.MultiValueMap;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.client.RestTemplate;
import org.springframework.web.multipart.MultipartFile;

import java.io.File;
import java.io.IOException;
import java.net.URI;
import java.net.URISyntaxException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.nio.file.StandardCopyOption;
import java.util.List;

@RestController
@RequestMapping("/file")
@Data
@ConfigurationProperties(prefix = "upload")
public class FileController {
    //服务器存储路径
    private String uploadDirectory;
    //文件大小
    private Long maxFileSize;
    //文件类型
    private List<String> fileType;
    //本地存储接口
    @Value("${remote.uploadurl}")
    private String uploadurl;
    @Value("${remote.exporturl}")
    private String exporturl;
    @Autowired
    private FileMapper fileMapper;
    @Autowired
    private RestTemplate restTemplate;
    @PostMapping("/upload")
    public String uploadFile(@RequestParam("file") MultipartFile file) throws IOException {
        //根据文件后缀判断存储方式
        String type = file.getOriginalFilename().substring(file.getOriginalFilename().lastIndexOf('.'));
        //如果文件较小且后缀满足条件,存储在服务器中
        if (file.getSize() < maxFileSize && !fileType.contains(type)) {
            try {
                // 构建文件保存路径
                Path uploadPath = Paths.get(uploadDirectory, file.getOriginalFilename());
                // 创建目录
                Files.createDirectories(uploadPath.getParent());
                // 将文件保存到磁盘
                Files.copy(file.getInputStream(), uploadPath, StandardCopyOption.REPLACE_EXISTING);

                FileEntity fileEntity = new FileEntity();
                fileEntity.setName(file.getOriginalFilename());
                fileEntity.setLocation("Server");
                fileMapper.insertFile(fileEntity);

                return "File uploaded successfully!";
            } catch (IOException e) {
                return "Error uploading file: " + e.getMessage();
            }
        }else {
            //文件存储在本地
            HttpHeaders headers = new HttpHeaders();
            headers.setContentType(MediaType.MULTIPART_FORM_DATA);

            MultiValueMap<String, Object> body = new LinkedMultiValueMap<>();
            body.add("file", file.getResource());

            HttpEntity<MultiValueMap<String, Object>> requestEntity = new HttpEntity<>(body, headers);

            ResponseEntity<String> response = restTemplate.exchange(
                    uploadurl,
                    HttpMethod.POST,
                    requestEntity,
                    String.class
            );
            return response.getBody();
        }
    }

    @GetMapping("/export")
    public ResponseEntity<Resource> exportFile(@RequestParam("fileName") String fileName) throws IOException, URISyntaxException {
        String location = fileMapper.findFile(fileName);
        //如果location等于server则从服务器路径下查找
        if ("Server".equals(location)){
            // 构建文件路径
            Path filePath = Paths.get(uploadDirectory, fileName);

            // 创建文件资源
            File file = filePath.toFile();
            InputStreamResource resource = new InputStreamResource(Files.newInputStream(file.toPath()));

            // 设置响应头
            HttpHeaders headers = new HttpHeaders();
            headers.add(HttpHeaders.CONTENT_DISPOSITION, "attachment; filename=\"" + file.getName() + "\"");
            headers.add(HttpHeaders.CONTENT_TYPE, Files.probeContentType(filePath));

            // 返回文件下载响应
            return ResponseEntity.ok()
                    .headers(headers)
                    .contentLength(file.length())
                    .contentType(MediaType.APPLICATION_OCTET_STREAM)
                    .body(resource);
        }else {
            //从本地路径下查找文件
            // 构建请求 URL
            URI uri = new URI(exporturl + "?fileName=" + fileName);

            // 发起 GET 请求并获取响应
            ResponseEntity<byte[]> response = restTemplate.getForEntity(uri, byte[].class);

            // 创建文件资源
            ByteArrayResource resource = new ByteArrayResource(response.getBody());

            // 设置响应头
            HttpHeaders headers = new HttpHeaders();
            headers.add(HttpHeaders.CONTENT_DISPOSITION, "attachment; filename=\"" + fileName + "\"");
            headers.add(HttpHeaders.CONTENT_TYPE, response.getHeaders().getContentType().toString());

            // 返回文件下载响应
            return ResponseEntity.ok()
                    .headers(headers)
                    .contentLength(resource.contentLength())
                    .contentType(MediaType.APPLICATION_OCTET_STREAM)
                    .body(resource);
        }

    }
}
